package com.alone.embedded.lucene.quickstart.spring;

import com.alone.embedded.lucene.bean.LatLon;
import com.alone.embedded.lucene.quickstart.Article;
import com.alone.embedded.lucene.repository.ElRepository;
import com.alone.embedded.lucene.repository.query.*;
import lombok.SneakyThrows;
import org.apache.lucene.search.SortField;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.context.ApplicationContext;

import java.util.Arrays;
import java.util.List;
import java.util.concurrent.Future;

/**
 * @author Alone
 * @date 2022/8/3 3:56 下午
 */
@SpringBootApplication
public class SpringLauncher {

    public static void main(String[] args) {
        ApplicationContext applicationContext = SpringApplication.run(SpringLauncher.class, args);

        ArticleService articleService = applicationContext.getBean(ArticleService.class);
        ElRepository<Article> repository = articleService.getRepository();

//        transaction(articleService, repository);
//        query(repository);

        demo(repository);

    }

    @SneakyThrows
    private static void demo(ElRepository<Article> repository) {

        // init data
        Future<Integer> future = repository.lambdaUpdate()
                .query(Querys.MATCH_ALL_QUERY)
                .deleteFuture();
        System.out.println("delete: " + future.get());
        repository.insert(Article.DATA);

        System.out.println("id = 4," + repository.selectDoc(4L).getMap());
        List<Article> articles = repository.selectList(
                Wrappers.<Article>lambdaQuery()
                        .like(Article::getAuthor, "第一军情｜环球时报")

        );
        for (Article article : articles) {
            System.out.println(article.getAuthor());
        }
        articles = repository.selectList(
                Wrappers.<Article>lambdaQuery()
                        .highlight()
                        .like(Article::getAuthor, "-第一军情 + -环球时报")

        );
        for (Article article : articles) {
            System.out.println(article);
        }


        System.out.println(repository.lambdaQuery()
                .highlight()
                .select(Article::getTitle, Article::getAuthor)
                .like(Article::getAuthor, "第*")
                .one());

        articles = repository.selectList(
                Wrappers.<Article>lambdaQuery()
                        .like(Article::getAuthor, "第一军~2")

        );

        Wrappers.<Article>lambdaQuery()
                .sortAsc(Article::getAuthor, SortField.Type.SCORE)
                .sortDesc(Article::getId, SortField.Type.LONG);

        for (Article article : articles) {
            System.out.println(article.getAuthor());
        }

        Sorts<Article> build = Sorts.<Article>builder()
                .asc(Article::getAuthor, SortField.Type.SCORE)
                .desc(Article::getId, SortField.Type.LONG)
                .build();


    }

    @SneakyThrows
    private static void transaction(ArticleService articleService, ElRepository<Article> repository) {
        List<Article> data = repository.selectList();
        System.out.println("查询行数：" + data.size());
        Future<Integer> deleteFuture = repository.deleteFuture(data);
        System.out.println("删除行数：" + deleteFuture.get());

        data = repository.selectList();
        int before = data.size();
        if (before == 0) {
            try {
                articleService.insert();
            } catch (Exception e) {
                e.printStackTrace();
            }
        }
        data = repository.selectList();
        System.err.println("------------");
        System.err.println("插入前数据条数：" + before);
        System.err.println("插入后数据条数：" + data.size());
        System.err.println("------------");
    }

    @SneakyThrows
    private static void query(ElRepository<Article> repository) {
        //
//        Wrappers.lambdaQuery()
//
//                // 默认样式
//                .highlight()
//                // 自定义样式
//                .highlight(Formatter formatter)
//
//                .sortAsc(C column, SortField.Type type)
//                .sortDesc(C column, SortField.Type type)
//                // 等于
//                .eq(C column, Object value)
//                // 小于等于
//                .le(C column, Object value)
//                // 大于等于
//                .ge(C column, Object value)
//                // 小于
//                .lt(C column, Object value)
//                // 大于
//                .gt(C column, Object value)
//                // 不等于
//                .ne(C column, Object value)
//                // 相当于或拼接的eq
//                .in(C column, Collection<?> value)
//                .notIn(C column, Collection<?> value)
//                //
//                .like(C column, Object value)
//                .notLike(C column, Object value)
//                // 原生查询
//                .query(Query query)
//                .query(Query query, BooleanClause.Occur occur)
//
//                // 只在selectList时生效
//                .limit(int limit)

        // init data
        List<Article> data = repository.selectList();
        repository.delete(data);
        repository.insert(Article.DATA);

        repository.selectList(Wrappers.<Article>lambdaQuery()
                .query(Querys.latLonBox(
                        Article::getLatLon,
                        LatLon.of(29.0, 120.0),
                        LatLon.of(30.0, 121.0))));

        repository.selectList(Wrappers.<Article>lambdaQuery()
                .query(Querys.latLonRadio(
                        Article::getLatLon,
                        LatLon.of(29.0, 120.0),
                        100000.0)));

        List<Article> articles = repository.selectList(Wrappers.<Article>lambdaQuery()
                .highlight()
                .in(Article::getAuthor, Arrays.asList("第一军情", "环球时报"))
                .like(Article::getTitle, "银保监会")
        );
        System.err.println("------------");
        for (Article article : articles) {
            System.err.println("author:" + article.getAuthor());
            System.err.println("title:" + article.getTitle());
        }
        System.err.println("------------");

        Page<Article> sortPage = repository.selectPage(
                Wrappers.<Article>lambdaQuery()
                        .sortDesc(Article::getId, SortField.Type.LONG),
                PageQuery.of(1, 3)
        );
        for (Article article : sortPage.getRecords()) {
            System.err.println("id:" + article.getId());
        }
        System.err.println("------------");
    }
}